package pro.seac.twitter.web.view;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;

import pro.seac.twitter.application.UserManagementService;
import pro.seac.twitter.application.dto.UserAccountData;
import pro.seac.twitter.web.ApplicationUI;
import pro.seac.twitter.web.ApplicationView;

import com.vaadin.navigator.ViewChangeListener.ViewChangeEvent;
import com.vaadin.shared.ui.label.ContentMode;
import com.vaadin.ui.Alignment;
import com.vaadin.ui.Button;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.Button.ClickListener;
import com.vaadin.ui.Component;
import com.vaadin.ui.HorizontalLayout;
import com.vaadin.ui.Label;
import com.vaadin.ui.VerticalLayout;
import com.vaadin.ui.themes.Reindeer;

public class BaseView extends ApplicationView {
	private static final long serialVersionUID = 1L;
	private Label titleLabel;
	@Autowired
	private UserManagementService service;

	@Override
	public void enter(ViewChangeEvent event) {
		initComponents();
	}

	protected void initComponents() {
		UserAccountData logged = getCurrentUser();
		VerticalLayout mainLayout = new VerticalLayout();
		mainLayout.setStyleName(Reindeer.LAYOUT_BLUE);
		mainLayout.setSizeFull();
		mainLayout.setSpacing(true);
		mainLayout.setMargin(true);
		{// *** header
			HorizontalLayout container = new HorizontalLayout();
			container.setWidth(100, Unit.PERCENTAGE);
			{// *** title
				VerticalLayout titleContainer = new VerticalLayout();
				Label label = null;
				titleContainer.addComponent(label = new Label("twitter xs "));
				label.setWidth(100, Unit.PERCENTAGE);
				label.setStyleName(Reindeer.LABEL_H1);
				titleContainer.setComponentAlignment(label, Alignment.MIDDLE_LEFT);

				titleContainer.addComponent(label = new Label("extra small version of <b>wwww.twitter.com</b>", ContentMode.HTML));
				label.setWidth(100, Unit.PERCENTAGE);
				label.setStyleName(Reindeer.LABEL_SMALL);
				titleContainer.setComponentAlignment(label, Alignment.MIDDLE_LEFT);

				container.addComponent(titleContainer);
				container.setExpandRatio(titleContainer, 1);
			}
			{// *** toolbar
				Component toolbar = logged == null ? initPublicToolbar() : initUserToolbar(logged);
				if (toolbar != null) container.addComponent(toolbar);
			}
			mainLayout.addComponent(container);
			{// *** menu
				HorizontalLayout menu = new HorizontalLayout();

				menu.setSpacing(true);
				initMenu(menu, logged);
				mainLayout.addComponent(menu);
			}

		}
		{// *** content
			VerticalLayout container = new VerticalLayout();
			container.setStyleName(Reindeer.LAYOUT_WHITE);
			container.setMargin(true);
			container.setSpacing(true);
			container.setSizeFull();

			container.addComponent(titleLabel = new Label(getTitle()));
			titleLabel.setWidth(100, Unit.PERCENTAGE);
			titleLabel.setStyleName(Reindeer.LABEL_H2);

			Label label = null;
			container.addComponent(label = new Label("<hr/>", ContentMode.HTML));
			label.setWidth(100, Unit.PERCENTAGE);
			label.setStyleName(Reindeer.LABEL_H2);
			Component contentContainer = initContent();
			if (contentContainer != null) {
				container.addComponent(contentContainer);
				container.setExpandRatio(contentContainer, 1);
			}
			mainLayout.addComponent(container);
			mainLayout.setExpandRatio(container, 1);
		}
		setCompositionRoot(mainLayout);
	}

	protected Component initPublicToolbar() {
		HorizontalLayout toolbarContainer = new HorizontalLayout();
		toolbarContainer.setSpacing(true);
		toolbarContainer.setSizeUndefined();
		toolbarContainer.addComponent(createButton("zapisz si\u0119", new ClickListener() {
			private static final long serialVersionUID = 1L;

			@Override
			public void buttonClick(ClickEvent event) {
				goToSignupView();
			}
		}));
		toolbarContainer.addComponent(createButton("zaloguj si\u0119", new ClickListener() {
			private static final long serialVersionUID = 1L;

			@Override
			public void buttonClick(ClickEvent event) {
				goToLoginView();
			}
		}));
		return toolbarContainer;
	}

	protected Component initUserToolbar(UserAccountData user) {
		HorizontalLayout toolbarContainer = new HorizontalLayout();
		toolbarContainer.setSpacing(true);
		toolbarContainer.setSizeUndefined();
		toolbarContainer.addComponent(new Label("@" + user.getUsername()));
		toolbarContainer.addComponent(createButton("wyloguj", new ClickListener() {
			private static final long serialVersionUID = 1L;

			@Override
			public void buttonClick(ClickEvent event) {
				logout();
			}
		}));
		return toolbarContainer;
	}

	protected Component initContent() {
		VerticalLayout contentContainer = new VerticalLayout();
		contentContainer.setSpacing(true);
		return contentContainer;
	}

	private void initMenu(HorizontalLayout container, UserAccountData user) {
		container.setWidth("100%");
		container.addComponent(createButton("g\u0142\u00F3wna", new ClickListener() {
			private static final long serialVersionUID = 1L;

			@Override
			public void buttonClick(ClickEvent event) {
				goToPublicHomeView();
			}
		}));
		container.addComponent(createButton("u\u017Cytkownicy", new ClickListener() {
			private static final long serialVersionUID = 1L;

			@Override
			public void buttonClick(ClickEvent event) {
				goToPublicUsersView();
			}
		}));
		if (user != null) {
			HorizontalLayout userMenu = new HorizontalLayout();
			userMenu.setSpacing(true);
			userMenu.addComponent(createButton("domowa", new ClickListener() {
				private static final long serialVersionUID = 1L;

				@Override
				public void buttonClick(ClickEvent event) {
					goToUserHomeView();
				}
			}));
			userMenu.addComponent(createButton("m\u00F3wi\u0105 o mnie", new ClickListener() {
				private static final long serialVersionUID = 1L;

				@Override
				public void buttonClick(ClickEvent event) {
					goToUserMentionView();
				}
			}));
			userMenu.addComponent(createButton("konto", new ClickListener() {
				private static final long serialVersionUID = 1L;

				@Override
				public void buttonClick(ClickEvent event) {
					goToUserAccountView();
				}
			}));
			container.addComponent(userMenu);
			container.setComponentAlignment(userMenu, Alignment.MIDDLE_RIGHT);
			container.setExpandRatio(userMenu, 1);
		} else {
			Label spacer = new Label();
			container.addComponent(spacer);
			container.setExpandRatio(spacer, 1);
		}
	}

	protected String getTitle() {
		return "";
	}

	protected void changeTitle(String newTitle) {
		titleLabel.setValue(newTitle);
	}

	public void goToLoginView() {
		ApplicationUI.goToView("login");
	}

	public void goToPublicHomeView() {
		ApplicationUI.goToView("");
	}

	public void goToPublicUsersView() {
		ApplicationUI.goToView("users");
	}

	public static void goToUsersProfileView(String username) {
		ApplicationUI.goToView("users/" + username);
	}

	public void goToSignupView() {
		ApplicationUI.goToView("signup");
	}

	public void goToUserHomeView() {
		ApplicationUI.goToView("home");
	}

	public void goToUserMentionView() {
		ApplicationUI.goToView("mention");
	}

	public void goToUserAccountView() {
		ApplicationUI.goToView("account");
	}

	public UserAccountData getCurrentUser() {
		Authentication auth = SecurityContextHolder.getContext().getAuthentication();
		return (UserAccountData) (auth != null ? auth.getPrincipal() : null);
	}

	public Integer getCurrentUserId() {
		UserAccountData u = getCurrentUser();
		return u == null ? null : u.getId();
	}

	public void logout() {
		SecurityContextHolder.clearContext();
		goToPublicHomeView();
	}

	protected Button createButton(String label, ClickListener listener) {
		Button button = new Button(label);
		button.setStyleName(Reindeer.BUTTON_SMALL);
		if (listener != null) button.addClickListener(listener);
		return button;
	}
}
